/**
 * @file main.c
 * @author your name (you@domain.com)
 * @brief 
 * @version 0.1
 * @date 2025-04-23
 * 
 * @copyright Copyright (c) 2025
 * 
 */

#include <rtthread.h>
#include "bsp_config.h"
#include "drv_uart.h"
#include "n32g003.h"
#include "flexible_button.h"

struct rt_timer timer_led1;
struct rt_timer timer_led2;
int SystemState = 0;

void led2_light_on(uint32_t time);


static flex_button_t user_button[1];

static uint8_t common_btn_read(void *arg)
{
    uint8_t value = 0;

    flex_button_t *btn = (flex_button_t *)arg;

    switch (btn->id)
    {
    case 0:
        value = GPIO_Input_Pin_Data_Get(KEY_WKUP_PORT, KEY_WKUP_PIN);
        break;
    default:
        RT_ASSERT(0);
    }

    return value;
}

static void btn1_evt_cb(void *arg)
{
    flex_button_t *btn = (flex_button_t *)arg;
    uint32_t val = 0;

    rt_kprintf("btn event: %d\r\n", btn->event);

    if (btn->event == FLEX_BTN_PRESS_CLICK)
    {
        if(SystemState == 0) return;
        led2_light_on(1000);
    }
    else if(btn->event == FLEX_BTN_PRESS_DOUBLE_CLICK)
    {
        if(SystemState == 0) return;
        rt_timer_control(&timer_led1, RT_TIMER_CTRL_GET_STATE, &val);
        if(val == RT_TIMER_FLAG_ACTIVATED)
        {
            rt_timer_stop(&timer_led1);
            GPIO_Pins_Set(LED1_PORT, LED1_PIN);
        }
        else
        {
            rt_timer_start(&timer_led1);
        }
    }
    else if(btn->event == FLEX_BTN_PRESS_LONG_START)
    {
        if(SystemState == 0)
        {
            SystemState = 1;
            rt_timer_start(&timer_led1);
        }
        else 
        {
            SystemState = 0;
            rt_timer_stop(&timer_led1);
            GPIO_Pins_Reset(LED1_PORT, LED1_PIN);     
        }
    }
}

static void user_button_init(void)
{
    rt_memset(&user_button[0], 0x0, sizeof(user_button));
    user_button[0].id = 0; 
    user_button[0].usr_button_read = common_btn_read; 
    user_button[0].cb = btn1_evt_cb; 
    user_button[0].pressed_logic_level = PIN_SET; 
    user_button[0].short_press_start_tick = FLEX_MS_TO_SCAN_CNT(1500); 
    user_button[0].long_press_start_tick = FLEX_MS_TO_SCAN_CNT(3000); 
    user_button[0].long_hold_start_tick = FLEX_MS_TO_SCAN_CNT(4500); 
    flex_button_register(&user_button[0]); 
}


void gpio_configuration(void)
{
    GPIO_InitType GPIO_InitStructure;
    
    /* 初始化GPIO结构体 */
    GPIO_Structure_Initialize(&GPIO_InitStructure);
    
    /* 配置LED控制引脚 */
    GPIO_InitStructure.Pin = LED1_PIN;
    GPIO_InitStructure.GPIO_Mode = GPIO_MODE_OUT_PP;
    GPIO_InitStructure.GPIO_Slew_Rate = GPIO_SLEW_RATE_FAST;
    GPIO_Peripheral_Initialize(LED1_PORT, &GPIO_InitStructure);    

    GPIO_InitStructure.Pin = LED2_PIN;
    GPIO_InitStructure.GPIO_Mode = GPIO_MODE_OUT_PP;
    GPIO_InitStructure.GPIO_Slew_Rate = GPIO_SLEW_RATE_FAST;
    GPIO_Peripheral_Initialize(LED2_PORT, &GPIO_InitStructure);    

    GPIO_InitStructure.Pin = KEY_WKUP_PIN;
    GPIO_InitStructure.GPIO_Mode = GPIO_MODE_INPUT;
    // GPIO_InitStructure.GPIO_Pull = GPIO_PULL_UP;
    GPIO_InitStructure.GPIO_Slew_Rate = GPIO_SLEW_RATE_FAST;
    GPIO_Peripheral_Initialize(KEY_WKUP_PORT, &GPIO_InitStructure);        
}

void rcc_configuration(void)
{
    RCC_APB_Peripheral_Clock_Enable(RCC_APB_PERIPH_IOPA);
}


void system_init(void)
{
    rcc_configuration();
    gpio_configuration();
}

void timer_led1_handler(void *parameter)
{
    static uint8_t led_state = 0;
    // rt_kprintf("led timer timeout\r\n");
    led_state ^= 1;

    if(led_state)
        GPIO_Pins_Set(LED1_PORT, LED1_PIN);
    else
        GPIO_Pins_Reset(LED1_PORT, LED1_PIN);
}

void timer_led2_handler(void *parameter)
{
    // rt_kprintf("led timer timeout\r\n");
    GPIO_Pins_Reset(LED2_PORT, LED2_PIN);
}

void led2_light_on(uint32_t time)
{
    rt_timer_control(&timer_led2, RT_TIMER_CTRL_SET_TIME, &time);

    GPIO_Pins_Set(LED2_PORT, LED2_PIN);
    rt_timer_start(&timer_led2);
}

int main(void)
{
    system_init();

    rt_timer_init(&timer_led1, "tmled1", timer_led1_handler, RT_NULL, 500, RT_TIMER_FLAG_PERIODIC);
    rt_timer_init(&timer_led2, "tmled2", timer_led2_handler, RT_NULL, 500, RT_TIMER_FLAG_ONE_SHOT);

    user_button_init();

    led2_light_on(500);

    while (1)
    {
        flex_button_scan();
        rt_thread_mdelay(20);
    }
}
